package com.hcc.flow.server.controller.workbench;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.alibaba.fastjson.JSONObject;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.hcc.flow.server.annotation.LogAnnotation;
import com.hcc.flow.server.annotation.Original;
import com.hcc.flow.server.common.constant.RedisKeyConstant;
import com.hcc.flow.server.common.enums.CheckStatusType;
import com.hcc.flow.server.common.enums.MsgType;
import com.hcc.flow.server.common.model.ApiResult;
import com.hcc.flow.server.common.page.table.PageTableHandler;
import com.hcc.flow.server.common.page.table.PageTableRequest;
import com.hcc.flow.server.common.page.table.PageTableResponse;
import com.hcc.flow.server.common.utils.CommUtil;
import com.hcc.flow.server.common.utils.StringUtilsV2;
import com.hcc.flow.server.dao.flowDesign.FlowDesignTempDao;
import com.hcc.flow.server.dao.sys.UserDao;
import com.hcc.flow.server.dao.workbench.MsgNoticeDao;
import com.hcc.flow.server.dao.workbench.MsgNoticeReadDao;
import com.hcc.flow.server.dto.sys.VerifyDto;
import com.hcc.flow.server.model.flowDesign.FlowDesignTemp;
import com.hcc.flow.server.model.workbench.MsgNotice;
import com.hcc.flow.server.model.workbench.MsgNoticeRead;
import com.hcc.flow.server.service.flowDesign.FlowService;
import com.hcc.flow.server.service.sys.RedisServer;
import com.hcc.flow.server.service.workbench.MsgNoticeService;
import com.hcc.flow.server.utils.UserUtil;
import com.hcc.flow.server.vo.workbench.MsgNoticeReadVO;
import com.hcc.flow.server.where.workbench.MsgNoticeReadWhere;

import io.swagger.annotations.ApiOperation;
import net.sf.json.util.JSONUtils;

/**
 * 消息阅读管理
 * @author 韩长志 20190604
 *
 */
@RestController
@RequestMapping("/msgNoticeReads")
public class MsgNoticeReadController {

    @Autowired
    private MsgNoticeReadDao msgNoticeReadDao;
    @Autowired
    private MsgNoticeDao msgNoticeDao;
    @Autowired
    private MsgNoticeService msgNoticeService;
    @Autowired
    private UserDao userDao;
    @Autowired
	private FlowDesignTempDao flowTempDao;
    @Autowired
    private FlowService flowService;
    
	@GetMapping("/read/{id}")
    @ApiOperation(value = "阅读某一个通知")
    //@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
    public ApiResult<?> read(@PathVariable String id) {
        if(StringUtilsV2.isBlank(id)){
			return ApiResult.error("要查询的id不能为空");
		}
        MsgNoticeRead msgNoticeRead= msgNoticeReadDao.getById(id);
        if(msgNoticeRead == null){
        	return ApiResult.error("要查询的通知数据不存在");
        }
        MsgNotice msgNotice = msgNoticeDao.getById(msgNoticeRead.getNoticeId());
        if(msgNotice == null){
        	return ApiResult.error("要查询的通知主数据不存在");
        }
        msgNoticeReadDao.updateRead(id);
        String taskType = MsgType.TASK.getCode().equals(msgNotice.getType())?msgNotice.getTaskType():"";
        RedisServer.remove(null,RedisKeyConstant.KEY_MSG_NOTICE+MsgType.getType(msgNotice.getType()).toString().toLowerCase()+taskType+":"+UserUtil.getLoginUser().getUserId());
    	return ApiResult.ok();
    }
	
	@GetMapping("/index/menu")
    @ApiOperation(value = "首页消息中心菜单")
    //@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
    public ApiResult<?> indexMenu(HttpServletRequest request) {
    	return ApiResult.data(userDao.getMsgMenuByUserId(UserUtil.getLoginUser().getUserId()));
    }
	
	@GetMapping("/index/show")
    @ApiOperation(value = "首页消息数")
    //@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
    public ApiResult<?> indexShow() {
		String readUserId = UserUtil.getLoginUser().getUserId();
    	return msgNoticeService.indexShow(readUserId);
    }
	
    @GetMapping("/{id}")
    @ApiOperation(value = "根据id获取")
    //@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
    public ApiResult<?> get(@PathVariable String id) {
        if(StringUtilsV2.isBlank(id)){
			return ApiResult.error("要查询的id不能为空");
		}
        MsgNoticeRead msgNoticeRead = msgNoticeReadDao.getById(id);
        if(msgNoticeRead == null){
        	return ApiResult.error("要查询的数据不存在");
        }
        MsgNotice msgNotice = msgNoticeDao.getById(msgNoticeRead.getNoticeId());
        if(msgNotice == null){
        	return ApiResult.error("要查询的通知主数据不存在");
        }
        msgNoticeReadDao.updateRead(id);//强制标为已读
        String taskType = MsgType.TASK.getCode().equals(msgNotice.getType())?msgNotice.getTaskType():"";
        RedisServer.remove(null,RedisKeyConstant.KEY_MSG_NOTICE+MsgType.getType(msgNotice.getType()).toString().toLowerCase()+taskType+":"+UserUtil.getLoginUser().getUserId());
    	return ApiResult.data(msgNoticeDao.getVoById(msgNoticeRead.getNoticeId(),id));
    }
	
    @LogAnnotation
    @DeleteMapping("/{id}")
    @ApiOperation(value = "逻辑删除")
    @PreAuthorize("hasAuthority('sys:msgNoticeRead:del')")
    public ApiResult<?> editStatusDelete(@PathVariable String id) {
    	if(StringUtilsV2.isBlank(id)){
    		return ApiResult.error("要删除的数据ID不能为空");
    	}
        msgNoticeReadDao.updateStatus(Arrays.asList(id),"3");
        return ApiResult.ok();
    }
    
    @PostMapping("/list")
	@ApiOperation(value = "列表（分页）")
	@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
	public PageInfo<MsgNoticeReadVO> ListNew(@RequestBody MsgNoticeReadWhere strCon) {
		PageHelper.startPage(strCon.getOffset(), strCon.getLimit());
		if (StringUtilsV2.isBlank(strCon.getSqlOrder())) {
			strCon.setSqlOrder("t.status,n.push_time desc ");
		}
		PageHelper.orderBy(strCon.getSqlOrder());
		strCon.setReadUserId(UserUtil.getLoginUser().getUserId());
		List<MsgNoticeReadVO> list = msgNoticeReadDao.MsgNoticeReadList(strCon);
		PageInfo<MsgNoticeReadVO> result = new PageInfo<MsgNoticeReadVO>(list);
		return result;
	}
    @GetMapping
	@ApiOperation(value = "列表-分页-2.0")
	@Original
	public PageTableResponse ListNew2(PageTableRequest  strCon) {
    	MsgNoticeReadWhere where = new MsgNoticeReadWhere(strCon);
		PageHelper.startPage(where.getOffset(), where.getLimit());
		if (StringUtils.isBlank(where.getSqlOrder())) {
			where.setSqlOrder("t.status,n.push_time desc ");
		}
		PageHelper.orderBy(where.getSqlOrder());
		where.setReadUserId(UserUtil.getLoginUser().getUserId());
		List<MsgNoticeReadVO> list = msgNoticeReadDao.MsgNoticeReadList(where);
		PageInfo<MsgNoticeReadVO> result = new PageInfo<MsgNoticeReadVO>(list);
		return new PageTableHandler(new PageTableHandler.CountHandler() {
			@Override
			public int count(PageTableRequest request) {
				return CommUtil.null2Int(result.getTotal());
			}
		}, new PageTableHandler.ListHandler() {
			@Override
			public List<MsgNoticeReadVO> list(PageTableRequest request) {
				return result.getList();
			}
		}).handle(strCon);
	}
    @GetMapping("/verify/list/{readId}")
	@ApiOperation(value = "审批记录-列表不分页")
	//@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
	public ApiResult<?> ListNew(@PathVariable String readId) {
    	if(readId == null) {
    		return ApiResult.error("请传入readId");
    	}
    	MsgNoticeRead read = msgNoticeReadDao.getById(readId);
    	if(read == null) {
    		return ApiResult.error("该任务不存在");
    	}
    	MsgNotice msgNotice = msgNoticeDao.getById(read.getNoticeId());
    	if(msgNotice == null) {
    		return ApiResult.error("该任务不存在");
    	}
    	List<MsgNoticeReadVO> result = new ArrayList<MsgNoticeReadVO>();
    	if(MsgType.RESULT.getCode().equals(msgNotice.getType()) && StringUtilsV2.isBlank(msgNotice.getFlowTempId())) {
    		msgNotice = msgNoticeDao.getMaxNewByFlowFromId(msgNotice.getFlowFromId(),msgNotice.getFlowSubmitNo(),msgNotice.getFlowTempId(),msgNotice.getFlowTempNodeId());
    		if(msgNotice == null) {
    			return ApiResult.data(result);
    			//return ApiResult.error("该结果消息对应任务不存在");
    		}
    	}
    	FlowDesignTemp temp = flowTempDao.getById(msgNotice.getFlowTempId());
    	if(temp == null) {
    		return ApiResult.error("该任务对应流程模板不存在");
    	}
    	JSONObject flow = null;
		if(StringUtilsV2.isNotBlank(temp.getFlowData())) {
			if(JSONUtils.mayBeJSON(temp.getFlowData())) {
				flow = JSONObject.parseObject(temp.getFlowData());
			}else {
				return ApiResult.error("流程副本("+temp.getFlowName()+")设计内容格式不是JSON格式");
			}
		}
		if(flow == null) {
			return ApiResult.error("流程副本("+temp.getFlowName()+")设计不能为空");
		}
		
    	List<MsgNoticeReadVO> list = msgNoticeDao.getNoticeReadVOByMore(msgNotice.getFlowFromId(),msgNotice.getFlowSubmitNo(),msgNotice.getFlowTempId(),null,true,2);
    	
    	ApiResult<JSONObject> ar;
    	JSONObject node;
    	for (MsgNoticeReadVO msgNoticeReadVO : list) {
    		ar = flowService.getNode(flow, null, msgNoticeReadVO.getFlowTempNodeId());
			if(!ar.isSuccess()) {
				return ar;
			}
			node = ar.getData();//当前节点
			msgNoticeReadVO.setTitle(node.getString("name"));
			if(msgNoticeReadVO.getReadTime() == null) {
				int verifyType = node.getIntValue("verifyType");//节点审核类型
				String verifyTypeStr = "";
				if(verifyType == 3) {
					verifyTypeStr = "用户";
				}else if(verifyType == 2) {
					verifyTypeStr = "角色";
				}else {
					verifyTypeStr = "机构";
				}
				msgNoticeReadVO.setReadUserName(verifyTypeStr+"-"+"["+node.getString("verifyModelNames")+"]");
				msgNoticeReadVO.setFlowVerifyStatusName(CheckStatusType.WAIT_AUDITED.getName());
				msgNoticeReadVO.setFlowVerifyReason("等待该节点相关任务归属者审核中");
			}
			result.add(msgNoticeReadVO);
		}
		return ApiResult.data(result);
	}
	
	@LogAnnotation
	@PostMapping("/read/verify")
	@ApiOperation(value = "流程节点-审核（通过/驳回/转办）")
	public ApiResult<?> audited(@RequestBody VerifyDto verifyDto) {
		if (verifyDto == null) {
			return ApiResult.error("审核信息不能为空");
		}
		if (StringUtilsV2.isBlank(verifyDto.getReadId())) {
			return ApiResult.error("任务ID不能为空");
		}
		if(StringUtilsV2.isBlank(verifyDto.getVerifyType())) {
			return ApiResult.error("审核类型不能为空");
		}
		if(CheckStatusType.AUDITED.getCode().equals(verifyDto.getVerifyType())) {
			return msgNoticeService.flowAudited(verifyDto);
		}else if(CheckStatusType.REFUSED.getCode().equals(verifyDto.getVerifyType())) {
			return msgNoticeService.flowRefused(verifyDto);
		}else if(CheckStatusType.DOOFFICE.getCode().equals(verifyDto.getVerifyType())) {
			if(StringUtilsV2.isBlank(verifyDto.getDoofUserId())) {
				return ApiResult.error("转办给的用户id不能为空");
			}
			return msgNoticeService.flowDoof(verifyDto);
		}else {
			return ApiResult.error("目前VerifyType只能传入3(通过)/4(驳回)/6(转办)");
		}
	}
	
	@GetMapping("/read/detail/{readId}")
	@ApiOperation(value = "根据id获取")
	@PreAuthorize("hasAuthority('sys:msgNoticeRead:query')")
	public ApiResult<?> readGet(@PathVariable String readId) {
    	return msgNoticeService.readGet(readId);
	}
}
